using System;
using System.Collections;
using System.Collections.Generic;
using AppTableUtils;
using UnityEngine;
using UnityEngine.UI;
using TMPro;
using UnityEngine.Serialization;


public class TranslateText : MonoBehaviour
{
    [Header("是否使用翻译")]
    public bool use_translate = true;

    // [Header("翻译所有子节点")] public bool translate_all_sub_nodes = false;
    [Header("Debug模式")] public bool flag__debug = false;

    [Header("翻译编号")]
    public string code;

    [Header("是否用gameObject.name自动填充code")]
    public bool use_auto_code = false;

    [Header("是否根据默认text自动翻译")]
    public bool auto_translate = true;

    private string _flag__auto_trans = "auto_translate";

    private string abs_obj_path { get { return BdTools.get_abs_path_by_obj(gameObject); } }
    private string flag__auto_trans { get { return $"{_flag__auto_trans}__{abs_obj_path}"; } }
    
    string last_language;

    private string default_content;

    private string default_from_lang { get { return TranslatorManager.instance.default_from_language; }} 
    private string to_lang { get { return TranslatorManager.instance.language; }}

    public string current_obj_lang;
    
    string get_translated_text_by_content(string content)
    {
        if (default_from_lang == to_lang)
        {
            return default_content;
        }

        string from_lang = BdUtils.is_null(current_obj_lang) ? default_from_lang : current_obj_lang;
        
        var row = TableUtils.get(TranslatorManager.instance.translator_dt, select: $"{from_lang}='{content}'");
        
        BdUtils.assert(row, $" *** gameObject[{gameObject.name}] ---`[{from_lang}] -> [{to_lang}]`对应`row`为空? content: [{content}]");
        
        // BdUtils.log("*** row:", row, BdUtils.is_null(row));
        var _text = row[to_lang];
        BdUtils.assert(row, $" *** gameObject[{gameObject.name}] ---`[{from_lang}] -> [{to_lang}]`对应`text`为空? content: [{content}]", raise_error: flag__raise_error);
        
        string translated_text = BdUtils.conv_to_string(_text);
        return translated_text;
    }

    private bool flag__raise_error => TranslatorManager.instance.flag__raise_error_if_code_map_none;

    public void translate_text()
    {
        if (!use_translate)
            return;

        if (last_language == TranslatorManager.instance.language)
        {
            // if (flag__debug)  BdUtils.log($" *** gameObject.name[{gameObject.name}] --- return");
            return;
        }
        last_language = TranslatorManager.instance.language;

        Text old_text_comp = BdTools.get_component_in_obj_self_or_children<Text>(gameObject);

        TMP_Text new_text_comp = null;
        if (old_text_comp == null)
            new_text_comp = BdTools.get_component_in_obj_self_or_children<TMP_Text>(gameObject);

        BdUtils.assert(old_text_comp || new_text_comp, $"gameObject[{gameObject.name}] --- code[{code}]对应的`text_comp`为空?");
        
        // auto_trans
        string translated_text;
        if (code != flag__auto_trans)
        {
            translated_text = TranslatorManager.instance.get_translated_text_by_code(code);
            
            if (flag__debug) 
                BdUtils.log($" *** gameObject.name[{gameObject.name}], code[{code}] --- current_obj_lang[{current_obj_lang}] -> to_lang[{to_lang}] --- get_translated_text_by_code, translated_text: [{translated_text}]");
        }
        else
        {
            string content = new_text_comp != null ? new_text_comp.text : old_text_comp.text;
            
            if (BdUtils.is_null(default_content))
                default_content = content;
            translated_text = get_translated_text_by_content(content: content);
            
            if (flag__debug)
                BdUtils.log($" *** gameObject[{gameObject.name}], code[{code}] ---  current_obj_lang[{current_obj_lang}] -> to_lang[{to_lang}]  --- get_translated_text_by_content, translated_text: [{translated_text}]");
        }

        current_obj_lang = to_lang;

        if (!BdUtils.is_null(translated_text))
        {
            if (replace_listeners.Count > 0)
            {
                translated_text = replace_listeners[0](translated_text);
            }

            translated_text = TranslatorManager.instance.translate_template(translated_text);
            
            if (old_text_comp)
                old_text_comp.text = translated_text;
            else
                new_text_comp.text = translated_text;
        }
    }

    private void get_trans_code()
    {
        if (BdUtils.not_null(code))
            return;
        
        BdUtils.assert(use_auto_code == false || auto_translate == false, "`use_auto_code`和`auto_trans`不能同时选中!");

        if (use_auto_code)
            code = BdUtils.is_null(code) ? gameObject.name : code;

        if (auto_translate)
            code = flag__auto_trans;
        BdUtils.assert(code, $"gameObject[{abs_obj_path}]的code为空!");
    }

    private void Start()
    {
        get_trans_code();

        var comp = GetComponent<TranslateText>();
        if (!TranslatorManager.instance.translate_comp_dc.ContainsKey(code))
        {
            string abs_path = BdTools.get_abs_path_by_obj(gameObject);
            string msg = $"*** 翻译脚本重复挂载! abs_path: [{abs_path}]";
            BdUtils.assert(!TranslatorManager.instance.translate_comp_dc.ContainsValue(comp), msg);
            TranslatorManager.instance.translate_comp_dc.Add(code, comp);
        }

        // add_template_pretreat(my_replace_template_pretreat);
    }

    private void OnDestroy()
    {
        if (TranslatorManager.instance.translate_comp_dc.ContainsKey(code))
            TranslatorManager.instance.translate_comp_dc.Remove(code);
    }
    
    public delegate string IReplaceListener(string template);
    // 监听列表, 在切换语言后触发
    public static List<IReplaceListener> replace_listeners = new List<IReplaceListener>();

    public void add_template_pretreat(IReplaceListener method)
    {
        replace_listeners.Clear();
        replace_listeners.Add(method);
    }

    private void OnEnable()
    {
        get_trans_code();
        if (BdUtils.is_null(TranslatorManager.instance))
            return;
        if (current_obj_lang == to_lang)
        {
            return;
        }
        translate_text();
    }
    
    private void CheckIfDuplicate()
    {
        // 获取当前GameObject上挂载的所有相同类型的脚本
        var scripts = GetComponents<TranslateText>();

        string abs_path = BdTools.get_abs_path_by_obj(gameObject);
        
        // 如果大于1，说明存在重复挂载
        BdUtils.assert(scripts.Length <= 1, $"翻译脚本重复挂载! abs_path: [{abs_path}]");
    }

    private void Awake()
    {
        CheckIfDuplicate();
    }
}
